/**
 * 学习时长记录工具类
 * 提供通用的前端学习时长记录功能
 *
 *
 * @author ruoyi
 * @date 2025-09-25
 */
window.StudyTimeRecorder = (function () {
  // 资源类型常量
  const RESOURCE_TYPE = {
    VIDEO: "video", // 视频
    MATERIAL: "material", // 材料
    AUDIO: "audio", // 有声读物
    BOOK: "book", // 红色书籍
    REALTIME: "realtime", // 实时资料
  };

  // 当前活跃的学习记录
  let currentStudySession = null;

  /**
   * 开始学习记录
   *
   * @param {string} resourceType 资源类型
   * @param {number} resourceId 资源ID
   * @param {Object} options 选项参数
   * @param {function} options.onSuccess 成功回调
   * @param {function} options.onError 失败回调
   */
  function startStudy(resourceType, resourceId, options = {}) {
    console.log("startStudy 被调用:", { resourceType, resourceId, options });

    const defaults = {
      onSuccess: null,
      onError: null,
    };

    const opts = Object.assign({}, defaults, options);

    const requestData = {
      resourceType: resourceType,
      resourceId: resourceId,
    };

    console.log("准备发送请求到 /dj/study/time/start，数据:", requestData);

    // 构建请求URL，支持上下文路径
    var url = ctx + "dj/study/time/start";
    console.log("实际请求URL:", url);

    // 发送开始记录请求
    $.post(url, requestData)
      .done(function (response) {
        console.log("收到响应:", response);
        if (response.code === 0) {
          // 创建学习会话对象
          currentStudySession = {
            resourceType: resourceType,
            resourceId: resourceId,
            startTime: new Date().getTime(),
            options: opts,
          };

          // 设置页面卸载监听器
          setupUnloadListener();

          console.log("开始学习记录成功:", resourceType, resourceId);

          if (opts.onSuccess) {
            opts.onSuccess(response);
          }
        } else {
          console.error("开始学习记录失败:", response.msg, response);
          if (opts.onError) {
            opts.onError(response);
          }
        }
      })
      .fail(function (xhr, status, error) {
        console.error("开始学习记录请求失败:", {
          status: status,
          error: error,
          responseText: xhr.responseText,
          xhr: xhr,
        });
        if (opts.onError) {
          opts.onError({ code: 500, msg: "网络请求失败: " + error });
        }
      });
  }

  /**
   * 结束学习记录
   *
   * @param {boolean} isComplete 是否完成学习（可选，默认false）
   * @param {function} callback 回调函数
   */
  function endStudy(isComplete = false, callback) {
    console.log(
      "准备结束学习记录:",
      currentStudySession.resourceType,
      currentStudySession.resourceId
    );

    const session = currentStudySession;
    currentStudySession = null;

    var endUrl = ctx + "dj/study/time/end";
    console.log("结束学习记录请求URL:", endUrl);

    $.post(endUrl, {
      resourceType: session.resourceType,
      resourceId: session.resourceId,
      isComplete: isComplete,
    })
      .done(function (response) {
        console.log("结束学习记录响应:", response);
        console.log(
          "结束学习记录成功:",
          session.resourceType,
          session.resourceId
        );
        if (callback) callback(response);
      })
      .fail(function (xhr, status, error) {
        console.error("结束学习记录请求失败:", {
          status: status,
          error: error,
          responseText: xhr.responseText,
        });
        if (callback) callback({ code: 500, msg: "网络请求失败: " + error });
      });
  }

  /**
   * 同步结束学习记录（用于页面卸载）
   */
  function endStudySync() {
    if (!currentStudySession) {
      return;
    }

    const session = currentStudySession;
    currentStudySession = null;

    // 使用 navigator.sendBeacon 或同步 XMLHttpRequest
    const data = new FormData();
    data.append("resourceType", session.resourceType);
    data.append("resourceId", session.resourceId);
    data.append("isComplete", "false");

    var syncEndUrl = ctx + "dj/study/time/end";

    if (navigator.sendBeacon) {
      // 使用 sendBeacon API（推荐，专为页面卸载设计）
      navigator.sendBeacon(syncEndUrl, data);
    } else {
      // 降级到同步 XMLHttpRequest
      $.ajax({
        url: syncEndUrl,
        type: "POST",
        async: false,
        data: {
          resourceType: session.resourceType,
          resourceId: session.resourceId,
          isComplete: false,
        },
      });
    }

    console.log("同步结束学习记录:", session.resourceType, session.resourceId);
  }

  // 全局标志，避免重复设置监听器
  let unloadListenerSetup = false;

  /**
   * 设置页面卸载监听器
   */
  function setupUnloadListener() {
    if (unloadListenerSetup) {
      return; // 已经设置过监听器，避免重复
    }

    unloadListenerSetup = true;

    // 只在页面卸载时结束记录，不监听页面可见性
    window.addEventListener("beforeunload", function () {
      if (currentStudySession) {
        endStudySync();
      }
    });
  }

  /**
   * 更新学习位置
   *
   * @param {number} position 当前位置（秒）
   * @param {function} callback 回调函数
   */
  function updatePosition(position, callback) {
    if (!currentStudySession) {
      console.warn("没有活跃的学习会话，无法更新位置");
      if (callback) callback({ code: 400, msg: "没有活跃的学习会话" });
      return;
    }

    var updateUrl = ctx + "dj/study/time/updatePosition";

    $.post(updateUrl, {
      resourceType: currentStudySession.resourceType,
      resourceId: currentStudySession.resourceId,
      position: position,
    })
      .done(function (response) {
        console.log("更新学习位置成功:", position + "秒");
        if (callback) callback(response);
      })
      .fail(function (xhr, status, error) {
        console.error("更新学习位置失败:", {
          status: status,
          error: error,
          responseText: xhr.responseText,
        });
        if (callback) callback({ code: 500, msg: "网络请求失败: " + error });
      });
  }

  /**
   * 获取当前学习会话信息
   *
   * @returns {Object|null} 当前学习会话信息
   */
  function getCurrentSession() {
    return currentStudySession;
  }

  // 导出公共API
  return {
    // 常量
    RESOURCE_TYPE: RESOURCE_TYPE,

    // 核心方法
    start: startStudy,
    end: endStudy,
    endSync: endStudySync,
    updatePosition: updatePosition,

    // 辅助方法
    getCurrentSession: getCurrentSession,

    // 便捷方法（针对不同资源类型）
    startVideo: function (videoId, options) {
      return startStudy(RESOURCE_TYPE.VIDEO, videoId, options);
    },
    startMaterial: function (materialId, options) {
      return startStudy(RESOURCE_TYPE.MATERIAL, materialId, options);
    },
    startAudio: function (audioId, options) {
      return startStudy(RESOURCE_TYPE.AUDIO, audioId, options);
    },
    startBook: function (bookId, options) {
      return startStudy(RESOURCE_TYPE.BOOK, bookId, options);
    },
    startRealtime: function (realtimeId, options) {
      return startStudy(RESOURCE_TYPE.REALTIME, realtimeId, options);
    },
  };
})();
